package appLoader
{
	import appLoader.I_Configuration;
	import appLoader.I_Loader;
	import appLoader.LoaderAsset;
	import appLoader.data.BasicConfiguration;
	import appLoader.data.MasterConfig;
	import appLoader.dictionaries.DictionaryManager;
	import appLoader.displayAdmin.DisplayLoaderAdmin;
	import appLoader.displayAdmin.DisplayLoaderItem;
	import appLoader.soundLibrary.SoundAdmin;
	
	import flash.display.LoaderInfo;
	import flash.display.MovieClip;
	import flash.events.Event;
	import flash.events.IOErrorEvent;
	import flash.text.TextField;
	
	import mx.logging.ILogger;
	import mx.logging.Log;
	import mx.logging.LogEventLevel;
	
	//[SWF(width="1024", height="768", frameRate="30", backgroundColor="#000000")]
	public class AplicationLoader extends MovieClip
	{
		protected var _flashVars:LoaderInfo;
		protected var _parameters:Object;
		protected var _swfApp:DisplayLoaderItem;
		protected var _configuration:MasterConfig;
		protected var _configurationURL:String;
		protected var _dictionary:DictionaryManager;
		protected var _dictionaryKey:String;
		protected var _assets:Vector.<LoaderAsset>;
		protected var _typedAssets:Vector.<I_Configuration>;
		protected var _assetsURL:Array;
		protected var _progressText:TextField;
		protected var _infoContainer:MovieClip;
		protected var _appBackground:String;
		protected var _appBackgroundContainer:MovieClip;
		protected var _appBackgroundLoader:DisplayLoaderItem;
		protected var _loaderBackground:String;
		protected var _loaderBackgroundContainer:MovieClip;
		protected var _loaderBackgroundLoader:DisplayLoaderItem;
		protected var _appName:String;
		protected var _language:String;
		protected var _maskDefault:MovieClip;
		private var _masked:Boolean;
		private var _objectsToLoad:int;
		private var _partialPercent:int;
		private var _progress:int;
		protected static var logger:ILogger = Log.getLogger("appLoader.AplicationLoader");
		public static const ALL_LOADED:String="All Loaded";
		public static const LOADING:String="Loading";
		public static const DICTIONARY_LOADED:String="Dictionary Loaded";

		
		public function AplicationLoader()
		{
			logger.log(LogEventLevel.INFO, "AplicationLoader");
			_loaderBackgroundContainer = new MovieClip;
			_infoContainer = new MovieClip;
			_appBackgroundContainer = new MovieClip;
			//setupMask(this);
			_assets = new Vector.<LoaderAsset>();
			this.addEventListener(Event.ADDED_TO_STAGE, init);
		}
		
		protected function init(event:Event):void {
			logger.log(LogEventLevel.INFO, "appLoaderAdded");
		}
		
		protected function startLoader(newLoaderInfo:LoaderInfo, newAppName:String=null, newLanguage:String=null, newConfigURL:String=null, _newAssets:Vector.<LoaderAsset>=null):void {
			_objectsToLoad= _assets.length+1;
			
			flashVars=loaderInfo;
			if (appName==null){
				if (newAppName!=null) {
					appName=newAppName;
				}else {
					logger.log(LogEventLevel.ERROR, "Must Define a SWF File to init the aplication");
				}
				if (language==null){
					if (newLanguage!=null){
						language=newLanguage;
					}else{
						logger.log(LogEventLevel.ERROR, "Must Define an Language sufix to init the aplication");
					}
					if (configurationURL==null){
						if (newConfigURL!=null){
							configurationURL=newConfigURL;
							loadMasterConfiguration();
						}else{
							logger.log(LogEventLevel.ERROR, "Must define an XMLConfig path to init the aplication");
						}
					}
				}
			} else {
				loadMasterConfiguration();
			}
			if (_newAssets != null) {
				_assets = _newAssets;
			} else {
				logger.log(LogEventLevel.ERROR, "No assets defined");
			}
		}
		
		public function set flashVars(value:LoaderInfo):void {
			_flashVars=value;
			if (_flashVars!=null) {
				_parameters=_flashVars.parameters;
				appName = _parameters.appName;
				language = _parameters.language;
				configurationURL = _parameters.configurationURL;
			}
		}
		
		protected function loadMasterConfiguration(event:Event=null):void
		{
			configuration = MasterConfig.gett();
			MasterConfig.gett().addEventListener(MasterConfig.ON_CONFIG_DONE, loadDictionary);
			MasterConfig.gett().addEventListener(IOErrorEvent.IO_ERROR, throwError);
			MasterConfig.gett().initConfig(configurationURL, "./xml/Config.xml");  			
		}
		
		protected function loadDictionary(event:Event):void
		{			
			dictionary = DictionaryManager.gett();
			DictionaryManager.gett().addEventListener(DictionaryManager.ON_DICTIONARY_MANAGER_LOADED, initLoaderBackground);
			DictionaryManager.gett().init(MasterConfig.gett().table.getStringProperty(_dictionaryKey), language);
		}
		
		
		protected function initLoaderBackground(event:Event=null):void {
			addChild(_loaderBackgroundContainer);
			if (_loaderBackground!=null && MasterConfig.gett().table.getStringProperty(_loaderBackground)!="") {
				_loaderBackgroundLoader = new DisplayLoaderItem("loaderBackground", MasterConfig.gett().table.getStringProperty(_loaderBackground));
				_loaderBackgroundLoader.container=_loaderBackgroundContainer;
				_loaderBackgroundLoader.addEventListener(DisplayLoaderItem.LOAD_COMPLETE, initContent);
				setupMask(_loaderBackgroundContainer);
				_loaderBackgroundLoader.initLoad();
			} else {
				initContent();
			}
		}
		
		protected function initContent(event:Event=null):void
		{
			addChild(_infoContainer);
			addChild(_appBackgroundContainer);
			if (_appBackground!=null && MasterConfig.gett().table.getStringProperty(_appBackground)!="") {
				_appBackgroundLoader = new DisplayLoaderItem("appBackground", MasterConfig.gett().table.getStringProperty(_appBackground));
				_appBackgroundLoader.addEventListener(DisplayLoaderItem.LOAD_COMPLETE, loadSwfApp);
				_appBackgroundLoader.initLoad();
			}else{
				loadSwfApp();
			}
		}
		
		protected function loadSwfApp(event:Event=null):void {
			_swfApp = new DisplayLoaderItem("masterAplication", _appName);
			_swfApp.addEventListener(DisplayLoaderItem.LOAD_COMPLETE, loadAssets);
			if (_appName =="DEBUG") {
				loadAssets();
			} else {
				_swfApp.initLoad();
			}
			this.addEventListener(Event.ENTER_FRAME, globalProgressUpdate)
		}
		
		protected function globalProgressUpdate(event:Event):void
		{
			_partialPercent = 0;
			_partialPercent += _swfApp.percent;
			for (var i:int = 0; i < _assets.length; i++) 
			{
				_partialPercent += _assets[i].library.getPercentLoaded();
			}
			
			progress=_partialPercent/_objectsToLoad;
			dispatchEvent(new Event(AplicationLoader.LOADING));
			if (_progressText!=null) {
				_progressText.text = progress.toString();
			}
		}
		
		protected function loadAssets(event:Event=null):void {
			dispatchEvent(new Event(DICTIONARY_LOADED));
			if (_assets.length >0) {
				for (var i:int = 0; i < _assets.length; i++) 
				{
					_assets[i].config.initConfig(MasterConfig.gett().table.getStringProperty(_assets[i].config.link));
				}
				addEventListener(Event.ENTER_FRAME, checkConfigsLoaded);
			} else {
				loadComplete();
			}
		}
		
		private function checkConfigsLoaded(event:Event):void
		{
			var counter:int=0;
			for (var i:int = 0; i < _assets.length; i++) 
			{
				if (_assets[i].config.isLoaded()) {
					counter++;
				}
			} 
			if (counter ==_assets.length) {
				removeEventListener(Event.ENTER_FRAME, checkConfigsLoaded);
				loadLibrarys();
			}
		}
		
		private function loadLibrarys():void
		{

			for (var i:int = 0; i < _assets.length; i++) 
			{
				if(_assets[i].config.language == null) {
					_assets[i].config.language="";
				}
				if(_assets[i].config.parameterKey == null) {
					_assets[i].config.parameterKey="";
				}
				if(_assets[i].config.optional == null) {
					_assets[i].config.optional="";
				}
				
				for(var j:int=0; j<_assets[i].config.table.length(); j++) {

					_assets[i].library.setItem(_assets[i].config.table.getKeyByIndex(j).toString(), MasterConfig.gett().table.getStringProperty(_assets[i].config.parameterKey+_assets[i].config.language)+_assets[i].config.optional+_assets[i].config.table.getValueByIndex(j).toString());
				}
				_assets[i].library.initLoad();
			}
			addEventListener(Event.ENTER_FRAME, checkLibrarysLoaded);
		}
		
		
		private function checkLibrarysLoaded(event:Event):void
		{
			var counter:int=0;
			for (var i:int = 0; i < _assets.length; i++) 
			{
				if (_assets[i].library.isLoaded()) {
					counter++;
				}
			}
			if (counter ==_assets.length) {
				removeEventListener(Event.ENTER_FRAME, checkLibrarysLoaded);
				loadComplete();
			}
		}
		
		protected function loadComplete(event:Event=null):void
		{
			infoContainer.visible =false;
			loaderBackgroundContainer.visible =false;
			this.removeEventListener(Event.ENTER_FRAME, globalProgressUpdate)
			if(_appBackground!=null && MasterConfig.gett().table.getStringProperty(_appBackground)!="") {
				_appBackgroundLoader.container=_appBackgroundContainer;
				setupMask(_appBackgroundContainer);
				_appBackgroundLoader.addToStage();
				if (_appName !="DEBUG") {
					_swfApp.container=this;
					_swfApp.addToStage();
				}				
			} else {
				if (_appName !="DEBUG") {
					_swfApp.container=this;
					setupMask(this);
					_swfApp.addToStage();
				}	
			}
			dispatchEvent(new Event(AplicationLoader.ALL_LOADED));
		}
		
		protected function setupMask(mc:MovieClip):void {
			if (_masked) {
				_maskDefault = new MovieClip;
				_maskDefault.graphics.beginFill(0x000000, 1);
				if(this.stage == null){
					_maskDefault.graphics.drawRect(0, 0, 1024, 768);
				}else{
					_maskDefault.graphics.drawRect(0, 0, this.stage.stageWidth, this.stage.stageHeight);
				}
				_maskDefault.graphics.endFill();
				mc.mask=_maskDefault;
			}
		}

		
		protected function throwError(event:Event):void {
			// TODO Make de Error throw function
		}

		public function get appName():String
		{
			return _appName;
		}

		public function set appName(value:String):void
		{
			_appName = value;
		}

		public function get language():String
		{
			return _language;
		}

		public function set language(value:String):void
		{
			_language = value;
		}

		public function get infoContainer():MovieClip
		{
			return _infoContainer;
		}

		public function set infoContainer(value:MovieClip):void
		{
			_infoContainer = value;
		}

		public function get appBackground():String
		{
			return _appBackground;
		}

		public function set appBackground(value:String):void
		{
			_appBackground = value;
		}

		public function get configurationURL():String
		{
			return _configurationURL;
		}

		public function set configurationURL(value:String):void
		{
			_configurationURL = value;
		}

		public function get swfApp():DisplayLoaderItem
		{
			return _swfApp;
		}

		public function set swfApp(value:DisplayLoaderItem):void
		{
			_swfApp = value;
		}

		public function get configuration():MasterConfig
		{
			return _configuration;
		}

		public function set configuration(value:MasterConfig):void
		{
			_configuration = value;
		}

		public function get dictionary():DictionaryManager
		{
			return _dictionary;
		}

		public function set dictionary(value:DictionaryManager):void
		{
			_dictionary = value;
		}

		public function get objectsToLoad():int
		{
			return _objectsToLoad;
		}

		public function set objectsToLoad(value:int):void
		{
			_objectsToLoad = value;
		}

		public function get progress():int
		{
			return _progress;
		}

		public function set progress(value:int):void
		{
			_progress = value;
		}

		public function get progressText():TextField
		{
			return _progressText;
		}

		public function set progressText(value:TextField):void
		{
			_progressText = value;
		}

		public function get loaderBackground():String
		{
			return _loaderBackground;
		}

		public function set loaderBackground(value:String):void
		{
			_loaderBackground = value;
		}

		public function get loaderBackgroundContainer():MovieClip
		{
			return _loaderBackgroundContainer;
		}

		public function set loaderBackgroundContainer(value:MovieClip):void
		{
			_loaderBackgroundContainer = value;
		}

		public function get masked():Boolean
		{
			return _masked;
		}

		public function set masked(value:Boolean):void
		{
			_masked = value;
		}

		public function get dictionaryKey():String
		{
			return _dictionaryKey;
		}

		public function set dictionaryKey(value:String):void
		{
			_dictionaryKey = value;
		}


	}
}